﻿package baidu.ui.controls
{
    import baidu.ui.controls.list.*;
    import baidu.ui.core.*;
    import baidu.ui.data.*;
    import baidu.ui.events.*;
    import flash.display.*;
    import flash.events.*;
    import flash.geom.*;
    import flash.text.*;

    public class ComboBox extends BUI
    {
        protected var textField:TextField;
        protected var background:Button;
        public var list:List;
        protected var isOpen:Boolean = false;
        protected var _rowCount:uint = 5;
        protected var _dropdownWidth:Number;
        public static var defaultStyles:Object = {skin:"ComboBox_Skin", buttonWidth:20, textPadding:2};

        public function ComboBox()
        {
            return;
        }// end function

        override public function get classStyles() : Object
        {
            return mergeStyles(super.classStyles, defaultStyles);
        }// end function

        override public function get enabled() : Boolean
        {
            return super.enabled;
        }// end function

        override public function set enabled(param1:Boolean) : void
        {
            super.enabled = param1;
            mouseEnabled = param1;
            this.background.enabled = param1;
            if (!param1)
            {
                this.close();
            }
            return;
        }// end function

        public function get rowCount() : int
        {
            return this._rowCount;
        }// end function

        public function set rowCount(param1:int) : void
        {
            this._rowCount = Math.max(1, param1);
            invalidate(Invalidation.SIZE);
            return;
        }// end function

        public function get selectedIndex() : int
        {
            return this.list.selectedIndex;
        }// end function

        public function set selectedIndex(param1:int) : void
        {
            this.list.selectedIndex = param1;
            invalidate(Invalidation.SELECTED);
            return;
        }// end function

        public function get selectedItem() : Object
        {
            return this.list.selectedItem;
        }// end function

        public function set selectedItem(param1:Object) : void
        {
            this.list.selectedItem = param1;
            invalidate(Invalidation.SELECTED);
            return;
        }// end function

        public function get dropdown() : List
        {
            return this.list;
        }// end function

        public function get length() : int
        {
            return this.list.length;
        }// end function

        public function get dataProvider() : DataProvider
        {
            return this.list.dataProvider;
        }// end function

        public function set dataProvider(param1:DataProvider) : void
        {
            param1.addEventListener(DataChangeEvent.DATA_CHANGE, this.handleDataChange, false, 0, true);
            this.list.dataProvider = param1;
            invalidate(Invalidation.DATA);
            return;
        }// end function

        public function get dropdownWidth() : Number
        {
            return this.list.width;
        }// end function

        public function set dropdownWidth(param1:Number) : void
        {
            this._dropdownWidth = param1;
            invalidate(Invalidation.SIZE);
            return;
        }// end function

        public function addItem(param1:Object) : void
        {
            this.list.addItem(param1);
            invalidate(Invalidation.DATA);
            return;
        }// end function

        public function addItemAt(param1:Object, param2:uint) : void
        {
            this.list.addItemAt(param1, param2);
            invalidate(Invalidation.DATA);
            return;
        }// end function

        public function removeAll() : void
        {
            this.list.removeAll();
            this.textField.text = "";
            invalidate(Invalidation.DATA);
            return;
        }// end function

        public function removeItem(param1:Object) : Object
        {
            return this.list.removeItem(param1);
        }// end function

        public function removeItemAt(param1:uint) : void
        {
            this.list.removeItemAt(param1);
            invalidate(Invalidation.DATA);
            return;
        }// end function

        public function getItemAt(param1:uint) : Object
        {
            return this.list.getItemAt(param1);
        }// end function

        public function replaceItemAt(param1:Object, param2:uint) : Object
        {
            return this.list.replaceItemAt(param1, param2);
        }// end function

        public function sortItems(... args)
        {
            return this.list.sortItems.apply(this.list, args);
        }// end function

        public function sortItemsOn(param1:String, param2:Object = null)
        {
            return this.list.sortItemsOn(param1, param2);
        }// end function

        public function open() : void
        {
            if (this.isOpen || this.length == 0)
            {
                return;
            }
            this.isOpen = true;
            if (stage)
            {
                stage.addEventListener(MouseEvent.MOUSE_DOWN, this.onStageClick, false, 0, true);
                this.adjustListPosition();
                this.list.scrollToSelected();
                stage.addChild(this.list);
            }
            dispatchEvent(new Event(Event.OPEN));
            return;
        }// end function

        public function close() : void
        {
            if (!this.isOpen)
            {
                return;
            }
            if (stage)
            {
                stage.removeEventListener(MouseEvent.MOUSE_DOWN, this.onStageClick);
                this.isOpen = false;
                if (stage.contains(this.list))
                {
                    stage.removeChild(this.list);
                }
            }
            dispatchEvent(new Event(Event.CLOSE));
            return;
        }// end function

        override protected function initUI() : void
        {
            super.initUI();
            setSize(100, 22);
            this.background = new Button();
            this.background.addEventListener(MouseEvent.MOUSE_DOWN, this.onToggleListVisibility, false, 0, true);
            addChild(this.background);
            this.textField = new TextField();
            addChild(this.textField);
            this.textField.mouseEnabled = false;
            this.list = new List();
            this.list.dataProvider.addEventListener(DataChangeEvent.DATA_CHANGE, this.handleDataChange, false, 0, true);
            this.list.addEventListener(Event.CHANGE, this.onListChange, false, 0, true);
            this.list.addEventListener(ListEvent.ITEM_CLICK, this.onListChange, false, 0, true);
            this.list.addEventListener(ListEvent.ITEM_ROLL_OUT, this.passEvent, false, 0, true);
            this.list.addEventListener(ListEvent.ITEM_ROLL_OVER, this.passEvent, false, 0, true);
            this.list.scrollPane.vScrollBar.addEventListener(Event.SCROLL, this.passEvent, false, 0, true);
            return;
        }// end function

        protected function handleDataChange(event:DataChangeEvent) : void
        {
            var _loc_2:* = this.selectedIndex;
            if (this.dataProvider.length == 0)
            {
                _loc_2 = Math.max(-1, Math.min(_loc_2, (this.length - 1)));
            }
            else
            {
                _loc_2 = Math.max(0, Math.min(_loc_2, (this.length - 1)));
            }
            if (this.list.selectedIndex != _loc_2)
            {
                this.list.selectedIndex = _loc_2;
                invalidate(Invalidation.SELECTED, false);
            }
            invalidate(Invalidation.DATA);
            return;
        }// end function

        override protected function draw() : void
        {
            var _loc_1:* = undefined;
            if (isInvalid(Invalidation.STYLES))
            {
                invalidate(Invalidation.SIZE, false);
                _loc_1 = getSkinInstance(getStyleValue("skin"));
                this.background.setStyle("skin", _loc_1);
            }
            if (isInvalid(Invalidation.SIZE, Invalidation.DATA, Invalidation.STATE))
            {
                this.drawTextFormat();
                this.drawLayout();
                invalidate(Invalidation.DATA);
            }
            if (isInvalid(Invalidation.DATA))
            {
                this.drawList();
                invalidate(Invalidation.SELECTED, true);
            }
            if (isInvalid(Invalidation.SELECTED))
            {
                if (this.selectedIndex == -1)
                {
                    this.textField.text = "";
                }
                else
                {
                    this.textField.text = this.list.selectedItem.label;
                }
            }
            super.draw();
            return;
        }// end function

        protected function drawLayout() : void
        {
            var _loc_1:* = getStyleValue("buttonWidth") as Number;
            var _loc_2:* = getStyleValue("textPadding") as Number;
            this.background.setSize(_width, _height);
            var _loc_3:* = _loc_2;
            this.textField.y = _loc_2;
            this.textField.x = _loc_3;
            this.textField.width = _width - _loc_1 - _loc_2;
            this.textField.height = _height - _loc_2;
            this.list.width = isNaN(this._dropdownWidth) ? (_width) : (this._dropdownWidth);
            this.background.enabled = this.enabled;
            this.background.drawNow();
            return;
        }// end function

        protected function drawTextFormat() : void
        {
            var _loc_1:* = getStyleValue(_enabled ? ("textFormat") : ("disabledTextFormat")) as TextFormat;
            if (_loc_1 == null)
            {
                _loc_1 = new TextFormat();
            }
            this.textField.defaultTextFormat = _loc_1;
            this.textField.setTextFormat(_loc_1);
            return;
        }// end function

        protected function drawList() : void
        {
            this.list.rowCount = Math.max(0, Math.min(this._rowCount, this.list.dataProvider.length));
            return;
        }// end function

        protected function adjustListPosition() : void
        {
            var _loc_1:* = localToGlobal(new Point(0, 0));
            this.list.x = _loc_1.x;
            if (_loc_1.y + height + this.list.height > stage.stageHeight)
            {
                this.list.y = _loc_1.y - this.list.height;
            }
            else
            {
                this.list.y = _loc_1.y + height;
            }
            return;
        }// end function

        protected function onToggleListVisibility(event:MouseEvent) : void
        {
            event.stopPropagation();
            dispatchEvent(event);
            if (this.isOpen)
            {
                this.close();
            }
            else
            {
                this.open();
                stage.addEventListener(MouseEvent.MOUSE_UP, this.onListItemUp, false, 0, true);
            }
            return;
        }// end function

        protected function onListItemUp(event:MouseEvent) : void
        {
            stage.removeEventListener(MouseEvent.MOUSE_UP, this.onListItemUp);
            if (!(event.target is IListCell) || !this.list.contains(event.target as DisplayObject))
            {
                return;
            }
            var _loc_2:* = this.selectedIndex;
            this.selectedIndex = event.target.listData.index;
            if (_loc_2 != this.selectedIndex)
            {
                dispatchEvent(new Event(Event.CHANGE));
            }
            this.close();
            return;
        }// end function

        protected function onListChange(event:Event) : void
        {
            dispatchEvent(event);
            invalidate(Invalidation.SELECTED);
            this.close();
            return;
        }// end function

        protected function onStageClick(event:MouseEvent) : void
        {
            if (!this.isOpen)
            {
                return;
            }
            if (!contains(event.target as DisplayObject) && !this.list.contains(event.target as DisplayObject))
            {
                this.close();
            }
            return;
        }// end function

        protected function passEvent(event:Event) : void
        {
            dispatchEvent(event);
            return;
        }// end function

    }
}
